package com.novoda.runbuddy.model;

import java.text.DecimalFormat;
import java.text.SimpleDateFormat;
import java.util.Calendar;
import java.util.Collection;
import java.util.GregorianCalendar;
import java.util.Iterator;
import java.util.LinkedList;
import java.util.List;
import java.util.Map;
import java.util.Map.Entry;

import android.location.Location;
import android.net.ParseException;

import com.novoda.runbuddy.activity.stopwatch.StopwatchTools;

public class ListOfRuns extends LinkedList<Run> {

	private static final String	DISPLAY_ZERO_TIME	= "00:00:00.00";
	
	@Override
	public void clear() {
		totalRunningTime = 0L;
		result = "";
		super.clear();
	}

	private static final long	serialVersionUID	= 23232L;
	private long				totalRunningTime	= 0L;
	private SimpleDateFormat	showingDateFormatter;
	GregorianCalendar			totalTime;
	String						result				= "";

	public boolean add(Run run) {
		long timeToAdd = StopwatchTools.getDiffMilli(run.getStartTime(), run.getStopTime());
		totalRunningTime = totalRunningTime + timeToAdd;

		return super.add(run);
	}

	public String getTotalRunningTime() {
		totalTime = new GregorianCalendar();
		totalTime.setTimeInMillis(totalRunningTime);

		if (totalTime.get(Calendar.HOUR) > 0) {
			totalTime.set(Calendar.HOUR, totalTime.get(Calendar.HOUR) - 1);
		}

		showingDateFormatter = new SimpleDateFormat("HH:mm:ss:SS");

		try {
			result = new String(showingDateFormatter.format(totalTime.getTime()));

		} catch (ParseException e) {
			System.out.println("Totalling the date failed");
			e.printStackTrace();
		}

		return result;
	}

	@Override
	public String[][] toArray() {
		int size = super.size();
		int runNo = 0;
		String[][] arrayOfRuns = new String[size][];
		StringBuffer coOrdinates;
		Iterator<Run> i = super.listIterator();
		DecimalFormat myFormatter = new DecimalFormat("0.000000");

		while (i.hasNext()) {
			Run run = (Run) i.next();
			String curr[] = new String[2];
			Map<Long, Location> loc = run.getlocationsAndTimes();
			coOrdinates = new StringBuffer();

			curr[0] = new String(run.name);
			int noOfLocations = loc.entrySet().size();
			int curentLoc = 0;

			for (Entry<Long, Location> location : loc.entrySet()) {
				if (curentLoc == noOfLocations - 1) {
					coOrdinates.append(myFormatter.format((location.getValue().getLongitude() / 1000000)) + ","
							+ myFormatter.format((location.getValue().getLatitude() / 1000000)));
				} else {
					coOrdinates.append(myFormatter.format((location.getValue().getLongitude() / 1000000)) + ","
							+ myFormatter.format((location.getValue().getLatitude() / 1000000)) + ",");
				}
				curentLoc++;
			}

			curr[1] = new String(coOrdinates);

			arrayOfRuns[runNo] = curr;
			runNo++;
		}

		return arrayOfRuns;
	}

//	For New Run functionality	
	public String[][] RUNtoArray() {
		int size = super.size();
		int runNo = 0;
		String[][] arrayOfRuns = new String[size][];
		StringBuffer coOrdinates;
		Iterator<Run> i = super.listIterator();
		DecimalFormat myFormatter = new DecimalFormat("0.000000");

		while (i.hasNext()) {
			Run run = (Run) i.next();
			String curr[] = new String[2];
			List<RunSegment> runSegments = run.getRunSegments();
			coOrdinates = new StringBuffer();

			curr[0] = new String(run.name);
			int noOfLocations = runSegments.size();
			int curentLoc = 0;

			for (RunSegment segment : runSegments) {
				CheckPoint checkPoint = segment.getCheckPoint();
				Location location = checkPoint.getLocation();

				if (curentLoc == noOfLocations - 1) {
					coOrdinates.append(myFormatter.format((location.getLongitude() / 1000000)) + ","
							+ myFormatter.format((location.getLatitude() / 1000000)));
				} else {
					coOrdinates.append(myFormatter.format((location.getLongitude() / 1000000)) + ","
							+ myFormatter.format((location.getLatitude() / 1000000)) + ",");
				}
				curentLoc++;
			}

			curr[1] = new String(coOrdinates);

			arrayOfRuns[runNo] = curr;
			runNo++;
		}

		return arrayOfRuns;
	}	
	
	public Run getRunByName(String runName)
	{
		Run run = null;
		
		Iterator<Run> it = this.listIterator();
		while (it.hasNext())
		{
			Run currentRun = it.next();
			if (currentRun.name.compareTo(runName)==0)
			{
				run = currentRun;
				break;
			}
		}
		return run;
	}
	
	@Override
	public void add(int arg0, Run arg1) {
		super.add(arg0, arg1);
	}


	@Override
	public boolean addAll(Collection<? extends Run> arg0) {
		return super.addAll(arg0);
	}

	@Override
	public boolean addAll(int arg0, Collection<? extends Run> arg1) {
		return super.addAll(arg0, arg1);
	}

	public long getTotalRunningTimeAsLong() {
		long totalTime = 0L;
		for (Run run : this) {
			totalTime = run.getTotalTime();
		}

		return totalTime;
	}

	public String getTotalRunningTimeForDisplay() {

		long totalRunTime = 0L;
		String result = DISPLAY_ZERO_TIME;

		if (this.size() > 0) {

			for (Run run : this) {
				totalRunTime = totalRunTime + run.getTotalTime();
			}

			try {
				result = StopwatchTools.getTimeInExpectedFormat(totalRunTime);

			} catch (ParseException e) {
				System.out.println("Totalling the date failed");
				e.printStackTrace();
			}
			return result;

		} else {
			return DISPLAY_ZERO_TIME;
		}

	}
	
}
